home *** CD-ROM | disk | FTP | other *** search
/ Amiga Format CD 24 / Amiga Format AFCD24 (Feb 1998, Issue 108).iso / -in_the_mag- / emulation / amiga / uae-0.7.0b2 / src / uaelib.c < prev    next >
C/C++ Source or Header  |  1998-01-20  |  9KB  |  403 lines

  1. /*
  2.  * UAE - The U*nix Amiga Emulator
  3.  *
  4.  * UAE Library v0.1
  5.  *
  6.  * (c) 1996 Tauno Taipaleenmaki <tataipal@raita.oulu.fi>
  7.  *
  8.  * Change UAE parameters and other stuff from inside the emulation.
  9.  */
  10.  
  11. #include "sysconfig.h"
  12. #include "sysdeps.h"
  13.  
  14. #include <assert.h>
  15. #include <string.h>
  16.  
  17. #include "config.h"
  18. #include "options.h"
  19. #include "threaddep/penguin.h"
  20. #include "uae.h"
  21. #include "include/memory.h"
  22. #include "custom.h"
  23. #include "readcpu.h"
  24. #include "newcpu.h"
  25. #include "xwin.h"
  26. #include "autoconf.h"
  27. #include "disk.h"
  28. #include "debug.h"
  29. #include "gensound.h"
  30. #include "picasso96.h"
  31.  
  32. /*
  33.  * Returns UAE Version
  34.  */
  35. static uae_u32 emulib_GetVersion(void)
  36. {
  37.     return version;
  38. }
  39.  
  40. /*
  41.  * Resets your amiga
  42.  */
  43. static uae_u32 emulib_HardReset(void)
  44. {
  45.     uae_reset();
  46.     return 0;
  47. }
  48.  
  49. static uae_u32 emulib_Reset(void)
  50. {
  51.     uae_reset();
  52.     return 0;
  53. }
  54.  
  55. /*
  56.  * Enables SOUND
  57.  */
  58. static uae_u32 emulib_EnableSound (uae_u32 val)
  59. {
  60.     if (!sound_available || currprefs.produce_sound == 2)
  61.     return 0;
  62.  
  63.     currprefs.produce_sound = val;
  64.     return 1;
  65. }
  66.  
  67. /*
  68.  * Enables FAKE JOYSTICK
  69.  */
  70. static uae_u32 emulib_EnableJoystick (uae_u32 val)
  71. {
  72.     currprefs.fake_joystick = val;
  73.     return 1;
  74. }
  75.  
  76. /*
  77.  * Sets the framerate
  78.  */
  79. static uae_u32 emulib_SetFrameRate (uae_u32 val)
  80. {
  81.     if (val == 0)
  82.     return 0;
  83.     else if (val > 20)
  84.     return 0;
  85.     else {
  86.     currprefs.framerate = val;
  87.     return 1;
  88.     }
  89. }
  90.  
  91. /*
  92.  * Changes keyboard language settings
  93.  */
  94. static uae_u32 emulib_ChangeLanguage (uae_u32 which)
  95. {
  96.     if (which > 5)
  97.     return 0;
  98.     else {
  99.     switch (which) {
  100.      case 0:
  101.         currprefs.keyboard_lang = KBD_LANG_US;
  102.         break;
  103.      case 1:
  104.         currprefs.keyboard_lang = KBD_LANG_DE;
  105.         break;
  106.      case 2:
  107.         currprefs.keyboard_lang = KBD_LANG_SE;
  108.         break;
  109.      case 3:
  110.         currprefs.keyboard_lang = KBD_LANG_FR;
  111.         break;
  112.      case 4:
  113.         currprefs.keyboard_lang = KBD_LANG_IT;
  114.         break;
  115.      case 5:
  116.         currprefs.keyboard_lang = KBD_LANG_ES;
  117.         break;
  118.      default:
  119.         break;
  120.     }
  121.     return 1;
  122.     }
  123. }
  124.  
  125. /* The following ones don't work as we never realloc the arrays... */
  126. /*
  127.  * Changes chip memory size
  128.  *  (reboots)
  129.  */
  130. static uae_u32 emulib_ChgCMemSize (uae_u32 memsize)
  131. {
  132.     if (memsize != 0x80000 && memsize != 0x100000 &&
  133.     memsize != 0x200000) {
  134.     memsize = 0x200000;
  135.     fprintf(stderr, "Unsupported chipmem size!\n");
  136.     }
  137.     m68k_dreg(regs, 0) = 0;
  138.  
  139.     chipmem_size = memsize;
  140.     uae_reset();
  141.     return 1;
  142. }
  143.  
  144. /*
  145.  * Changes slow memory size
  146.  *  (reboots)
  147.  */
  148. static uae_u32 emulib_ChgSMemSize (uae_u32 memsize)
  149. {
  150.     if (memsize != 0x80000 && memsize != 0x100000 &&
  151.     memsize != 0x180000 && memsize != 0x1C0000) {
  152.     memsize = 0;
  153.     fprintf(stderr, "Unsupported bogomem size!\n");
  154.     }
  155.  
  156.     m68k_dreg(regs, 0) = 0;
  157.     bogomem_size = memsize;
  158.     uae_reset();
  159.     return 1;
  160. }
  161.  
  162. /*
  163.  * Changes fast memory size
  164.  *  (reboots)
  165.  */
  166. static uae_u32 emulib_ChgFMemSize (uae_u32 memsize)
  167. {
  168.     if (memsize != 0x100000 && memsize != 0x200000 &&
  169.     memsize != 0x400000 && memsize != 0x800000) {
  170.     memsize = 0;
  171.     fprintf(stderr, "Unsupported fastmem size!\n");
  172.     }
  173.     m68k_dreg(regs, 0) = 0;
  174.     fastmem_size = memsize;
  175.     uae_reset();
  176.     return 0;
  177. }
  178.  
  179. /*
  180.  * Inserts a disk
  181.  */
  182. static uae_u32 emulib_InsertDisk(uaecptr name, uae_u32 drive)
  183. {
  184.     int i = 0;
  185.     char real_name[256];
  186.  
  187.     if (drive > 3)
  188.     return 0;
  189.  
  190.     while ((real_name[i] = get_byte (name + i)) != 0 && i++ != 254)
  191.     ;
  192.  
  193.     if (i == 255)
  194.     return 0; /* ENAMETOOLONG */
  195.  
  196.     strcpy (changed_prefs.df[drive], real_name);
  197.  
  198.     return 1;
  199. }
  200.  
  201. /*
  202.  * Exits the emulator
  203.  */
  204. static uae_u32 emulib_ExitEmu(void)
  205. {
  206.     uae_quit ();
  207.     return 1;
  208. }
  209.  
  210. /*
  211.  * Gets UAE Configuration
  212.  */
  213. static uae_u32 emulib_GetUaeConfig(uaecptr place)
  214. {
  215.     int i,j;
  216.  
  217.     put_long(place     , version);
  218.     put_long(place +  4, chipmem_size);
  219.     put_long(place +  8, bogomem_size);
  220.     put_long(place + 12, fastmem_size);
  221.     put_long(place + 16, currprefs.framerate);
  222.     put_long(place + 20, currprefs.produce_sound);
  223.     put_long(place + 24, currprefs.fake_joystick);
  224.     put_long(place + 28, currprefs.keyboard_lang);
  225.     if (disk_empty(0))
  226.     put_byte(place + 32, 0);
  227.     else
  228.     put_byte(place + 32, 1);
  229.     if (disk_empty(1))
  230.     put_byte(place + 33, 0);
  231.     else
  232.     put_byte(place + 33, 1);
  233.     if (disk_empty(2))
  234.     put_byte(place + 34, 0);
  235.     else
  236.     put_byte(place + 34, 1);
  237.     if (disk_empty(3))
  238.     put_byte(place + 35, 0);
  239.     else
  240.     put_byte(place + 35, 1);
  241.  
  242.     for (i = 0; i < 256; i++) {
  243.     put_byte((place + 36 + i), currprefs.df[0][i]);
  244.     put_byte((place + 36 + i + 256), currprefs.df[1][i]);
  245.     put_byte((place + 36 + i + 512), currprefs.df[2][i]);
  246.     put_byte((place + 36 + i + 768), currprefs.df[3][i]);
  247.     }
  248.     return 1;
  249. }
  250.  
  251. /*
  252.  * Sets UAE Configuration
  253.  *
  254.  * NOT IMPLEMENTED YET
  255.  */
  256. static uae_u32 emulib_SetUaeConfig(uaecptr place)
  257. {
  258.     return 1;
  259. }
  260.  
  261. /*
  262.  * Gets the name of the disk in the given drive
  263.  */
  264. static uae_u32 emulib_GetDisk(uae_u32 drive, uaecptr name)
  265. {
  266.     int i;
  267.     if (drive > 3)
  268.     return 0;
  269.  
  270.     for (i = 0;i < 256; i++) {
  271.     put_byte (name + i, currprefs.df[drive][i]);
  272.     }
  273.     return 1;
  274. }
  275.  
  276. /*
  277.  * Enter debugging state
  278.  */
  279. static uae_u32 emulib_Debug(void)
  280. {
  281.     activate_debugger ();
  282.     return 1;
  283. }
  284.  
  285. /* We simply find the first "text" hunk, get the offset of its actual code segment (20 bytes away)
  286.  * and add that offset to the base address of the object.  Now we've got code to execute.
  287.  *
  288.  * @@@ Brian: does anything actually use this yet?
  289.  */
  290. static uae_u32 FindFunctionInObject (uae_u8 *objectptr)
  291. {
  292.     uae_u8 *text_hdr;
  293.     uae_u8 offset;
  294.     text_hdr = (uae_u8 *)strstr ("text", (char *)objectptr);
  295.     if (text_hdr != 0) {
  296.     offset = *(text_hdr + 19);
  297.     return (uae_u32)(objectptr + offset);
  298.     }
  299.     return 0;
  300. }
  301.  
  302. #define CREATE_NATIVE_FUNC_PTR uae_u32 (* native_func)( uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, \
  303.                          uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32)
  304. #define SET_NATIVE_FUNC(x) native_func = (uae_u32 (*)(uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32, uae_u32))(x)
  305. #define CALL_NATIVE_FUNC( d1,d2,d3,d4,d5,d6,d7,a1,a2,a3,a4,a5,a6 ) if(native_func) native_func( d1,d2,d3,d4,d5,d6,d7,a1,a2,a3,a4,a5,a6 )
  306. /* A0 - Contains a ptr to the native .obj data.  This ptr is Amiga-based. */
  307. /*      We simply find the first function in this .obj data, and execute it. */
  308. static uae_u32 emulib_ExecuteNativeCode(void)
  309. {
  310.     uaecptr object_AAM = m68k_areg( regs, 0 );
  311.     uae_u32 d1 = m68k_dreg( regs, 1 );
  312.     uae_u32 d2 = m68k_dreg( regs, 2 );
  313.     uae_u32 d3 = m68k_dreg( regs, 3 );
  314.     uae_u32 d4 = m68k_dreg( regs, 4 );
  315.     uae_u32 d5 = m68k_dreg( regs, 5 );
  316.     uae_u32 d6 = m68k_dreg( regs, 6 );
  317.     uae_u32 d7 = m68k_dreg( regs, 7 );
  318.     uae_u32 a1 = m68k_areg( regs, 1 );
  319.     uae_u32 a2 = m68k_areg( regs, 2 );
  320.     uae_u32 a3 = m68k_areg( regs, 3 );
  321.     uae_u32 a4 = m68k_areg( regs, 4 );
  322.     uae_u32 a5 = m68k_areg( regs, 5 );
  323.     uae_u32 a6 = m68k_areg( regs, 6 );
  324.  
  325.     uae_u8* object_UAM = NULL;
  326.     CREATE_NATIVE_FUNC_PTR;
  327.  
  328.     if( get_mem_bank( object_AAM ).check( object_AAM, 1 ) )
  329.     object_UAM = get_mem_bank( object_AAM).xlateaddr( object_AAM );
  330.  
  331.     if( object_UAM )
  332.     {
  333.     SET_NATIVE_FUNC( FindFunctionInObject( object_UAM ) );
  334.     CALL_NATIVE_FUNC( d1, d2, d3, d4, d5, d6, d7, a1, a2, a3, a4, a5, a6);
  335.     }
  336.     return 1;
  337. }
  338.  
  339. static uae_u32 uaelib_demux (void)
  340. {
  341. #define ARG0 (get_long (m68k_areg (regs, 7) + 4))
  342. #define ARG1 (get_long (m68k_areg (regs, 7) + 8))
  343. #define ARG2 (get_long (m68k_areg (regs, 7) + 12))
  344. #define ARG3 (get_long (m68k_areg (regs, 7) + 16))
  345.  
  346.     switch (ARG0) {
  347.      case 0: return emulib_GetVersion ();
  348.      case 1: return emulib_GetUaeConfig (ARG1);
  349.      case 2: return emulib_SetUaeConfig (ARG1);
  350.      case 3: return emulib_HardReset ();
  351.      case 4: return emulib_Reset ();
  352.      case 5: return emulib_InsertDisk (ARG1, ARG2);
  353.      case 6: return emulib_EnableSound (ARG1);
  354.      case 7: return emulib_EnableJoystick (ARG1);
  355.      case 8: return emulib_SetFrameRate (ARG1);
  356.      case 9: return emulib_ChgCMemSize (ARG1);
  357.      case 10: return emulib_ChgSMemSize (ARG1);
  358.      case 11: return emulib_ChgFMemSize (ARG1);
  359.      case 12: return emulib_ChangeLanguage (ARG1);
  360.     /* The next call brings bad luck */
  361.      case 13: return emulib_ExitEmu ();
  362.      case 14: return emulib_GetDisk (ARG1, ARG2);
  363.      case 15: return emulib_Debug ();
  364.  
  365. #ifdef PICASSO96
  366.      case 16: return picasso_FindCard();
  367.      case 17: return picasso_FillRect();
  368.      case 18: return picasso_SetSwitch();
  369.      case 19: return picasso_SetColorArray();
  370.      case 20: return picasso_SetDAC();
  371.      case 21: return picasso_SetGC();
  372.      case 22: return picasso_SetPanning();
  373.      case 23: return picasso_CalculateBytesPerRow();
  374.      case 24: return picasso_BlitPlanar2Chunky();
  375.      case 25: return picasso_BlitRect();
  376.      case 26: return picasso_SetDisplay();
  377.      case 27: return picasso_BlitTemplate();
  378.      case 28: return picasso_BlitRectNoMaskComplete();
  379.      case 29: return picasso_InitCard();
  380.      case 30: return picasso_BlitPattern();
  381.      case 31: return picasso_InvertRect();
  382.      case 32: return picasso_BlitPlanar2Direct();
  383.      case 34: return picasso_WaitVerticalSync();
  384.      case 35: return gfxmem_size ? 1 : 0;
  385. #endif
  386.  
  387.      case 69: return emulib_ExecuteNativeCode();
  388.     }
  389.     return 0;
  390. }
  391.  
  392. /*
  393.  * Installs the UAE LIBRARY
  394.  */
  395. void emulib_install(void)
  396. {
  397.     uaecptr a = here ();
  398.     org (0xF0FF60);
  399.     calltrap (deftrap (uaelib_demux));
  400.     dw (RTS);
  401.     org (a);
  402. }
  403.